package com.twetec.cms.service.file.impl;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.text.UnicodeUtil;
import cn.hutool.core.util.StrUtil;
import com.twetec.cms.common.util.file.FileTreeItem;
import com.twetec.cms.common.util.file.LocalFileUtil;
import com.twetec.cms.dao.mapper.website.SiteMapper;
import com.twetec.cms.dao.mapper.website.WebsiteTemplateMapper;
import com.twetec.cms.model.po.website.SitePO;
import com.twetec.cms.model.po.website.WebsiteTemplatePO;
import com.twetec.cms.model.vo.website.*;
import com.twetec.cms.service.file.LocalFileService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.nio.charset.Charset;
import java.util.ArrayList;

@Service
public class LocalFileServiceImpl implements LocalFileService {

    /**
     * 资源文件根目录
     */
    @Value("${twetec.resource.storage-root-path}")
    private String resourceStorageRootPath;

    /**
     * 资源文件地址
     */
    @Value("${twetec.resource.storage-root-url}")
    private String resourceStorageRootUrl;

    @Autowired
    private WebsiteTemplateMapper templateMapper;

    //
    @Autowired
    private SiteMapper siteMapper;

    @Override
    public TemplateTreeListVO getFileTreeListByTemplateId(Long templateId) {
        // 获取配置的根路径
        String templateRootPath = resourceStorageRootPath;
        WebsiteTemplatePO templatePO = templateMapper.selectById(templateId);
        SitePO sitePO = null;
        if (templatePO != null) sitePO = siteMapper.selectById(templatePO.getSiteId());
        if (sitePO != null) {
            // 根路径为：配置的根路径+站点id+template+模板编码
            templateRootPath = resourceStorageRootPath + File.separator + sitePO.getId() + File.separator +
                    "template" + File.separator + templatePO.getCode();
        }

        // 返回的对象
        TemplateTreeListVO templateTreeListVO = new TemplateTreeListVO();

        // 返回对象中的文件树
        ArrayList<TemplateTreeItemVO> templateTreeItemVOList = new ArrayList<>();

        // 根目录的file类
        File file = FileUtil.file(templateRootPath);

        // 如果文件路径不存在,或者是一个空目录
        if (!FileUtil.exist(templateRootPath) || FileUtil.isDirEmpty(file)) {

            // 如果文件路径不存在就先创建目录，再准备返回的对象
            if (!FileUtil.exist(templateRootPath)) FileUtil.mkdir(templateRootPath);

            // 文件树的内容
            TemplateTreeItemVO templateTreeItemVO = new TemplateTreeItemVO();

            // 文件树标题
            templateTreeItemVO.setTitle("根目录");

            // 文件信息
            FileInfoVO fileInfoVO = new FileInfoVO();
            // 名称
            fileInfoVO.setFileName("根目录");
            // 是文件还是文件夹
            fileInfoVO.setIsDir(1);
            // 设置绝对路径
            fileInfoVO.setAbsolutePath(file.getAbsolutePath());
            // 设置相对路径
//            fileInfoVO.setRelativePath();
            fileInfoVO.setSize(0L);

            // 文件树信息
            templateTreeItemVO.setFileInfo(fileInfoVO);
            // 子文件信息
            templateTreeItemVO.setChildList(new ArrayList());

            // 添加本颗文件树
            templateTreeItemVOList.add(templateTreeItemVO);

            // 设置文件树的集合
            templateTreeListVO.setTreeList(templateTreeItemVOList);
        } else {
            FileTreeItem fileTreeItem = new FileTreeItem();
            fileTreeItem.setIsDir(1);
            fileTreeItem.setFileName("根目录");
            fileTreeItem.setSize(FileUtil.size(file));
            fileTreeItem.setAbsolutePath(file.getAbsolutePath());
//            fileTreeItem.setRelativePath();
            // 获取文件树的方法
            LocalFileUtil.getFileTreeListByPath(templateRootPath,file, fileTreeItem);
            TemplateTreeItemVO templateTreeItemVO = new TemplateTreeItemVO();
            // 将文件树转化为VO
            String siteTemplateFilePath = File.separator + sitePO.getId() + File.separator + "template" + File.separator + templatePO.getCode();
            p_templateTreeToVO(fileTreeItem, templateTreeItemVO, siteTemplateFilePath);
            // 将vo添加到集合中
            templateTreeItemVOList.add(templateTreeItemVO);
            // 集合设置给封装对象
            templateTreeListVO.setTreeList(templateTreeItemVOList);
        }

        // 返回文件树
        return templateTreeListVO;

    }

    @Override
    public HtmlTemplateTreeListVO getHtmlFileTreeListByTemplateId(Long templateId) {
        // 获取配置的根路径
        String templateRootPath = resourceStorageRootPath;
        WebsiteTemplatePO templatePO = templateMapper.selectById(templateId);
        SitePO sitePO = null;
        if (templatePO != null) sitePO = siteMapper.selectById(templatePO.getSiteId());
        if (sitePO != null) {
            // 根路径为：配置的根路径+站点id+template+模板编码
            templateRootPath = resourceStorageRootPath + File.separator + sitePO.getId() + File.separator +
                    "template" + File.separator + templatePO.getCode();
        }

        // 返回的对象
        HtmlTemplateTreeListVO htmlTemplateTreeListVO = new HtmlTemplateTreeListVO();

        // 返回对象中的文件树
        ArrayList<HtmlTemplateTreeItemVO> htmlTemplateTreeItemVOList = new ArrayList<>();

        // 根目录的file类
        File file = FileUtil.file(templateRootPath);

        // 如果文件路径不存在,或者是一个空目录
        if (!FileUtil.exist(templateRootPath) || FileUtil.isDirEmpty(file)) {
            // 如果文件路径不存在就先创建目录，再准备返回的对象
            if (!FileUtil.exist(templateRootPath)) FileUtil.mkdir(templateRootPath);

            HtmlTemplateTreeItemVO htmlTemplateTreeItemVO = new HtmlTemplateTreeItemVO();
            htmlTemplateTreeItemVO.setTitle("根目录");
            htmlTemplateTreeItemVO.setExt("");
            htmlTemplateTreeItemVO.setIsDir(1);
            htmlTemplateTreeItemVO.setPath("");
            htmlTemplateTreeItemVO.setChildList(new ArrayList());

            // 添加本颗文件树
            htmlTemplateTreeItemVOList.add(htmlTemplateTreeItemVO);

            // 设置文件树的集合
            htmlTemplateTreeListVO.setTreeList(htmlTemplateTreeItemVOList);
        } else {

            FileTreeItem fileTreeItem = new FileTreeItem();
            fileTreeItem.setIsDir(1);
            fileTreeItem.setFileName("根目录");
            fileTreeItem.setSize(FileUtil.size(file));
            fileTreeItem.setAbsolutePath(file.getAbsolutePath());

            // 获取文件树的方法
            LocalFileUtil.getFileTreeListByPath(templateRootPath, file, fileTreeItem);
            HtmlTemplateTreeItemVO htmlTemplateTreeItemVO = new HtmlTemplateTreeItemVO();

            // 将文件树转化为VO
            String siteTemplateFilePath = File.separator + sitePO.getId() + File.separator + "template" + File.separator + templatePO.getCode();
            p_htmlTemplateTreeToVO(fileTreeItem, htmlTemplateTreeItemVO, siteTemplateFilePath);

            // 添加本颗文件树
            htmlTemplateTreeItemVOList.add(htmlTemplateTreeItemVO);

            // 设置文件树的集合
            htmlTemplateTreeListVO.setTreeList(htmlTemplateTreeItemVOList);
        }

        // 返回文件树
        return htmlTemplateTreeListVO;
    }


    /**
     * 将文件数转换为VO对象
     * @param fileTreeItem
     * @param templateTreeItemVO
     */
    private void p_templateTreeToVO(FileTreeItem fileTreeItem, TemplateTreeItemVO templateTreeItemVO, String templateRootPath) {
        // 设置vo的值
        templateTreeItemVO.setTitle(fileTreeItem.getFileName());

        // 设置fileInfoVO的属性
        FileInfoVO fileInfoVO = new FileInfoVO();
        fileInfoVO.setIsDir(fileTreeItem.getIsDir());
        if (null != fileTreeItem.getRelativePath()) {
            fileInfoVO.setUrl(resourceStorageRootUrl + templateRootPath + fileTreeItem.getRelativePath());
        }
        fileInfoVO.setFileName(fileTreeItem.getFileName());
        fileInfoVO.setAbsolutePath(fileTreeItem.getAbsolutePath());
        fileInfoVO.setRelativePath(fileTreeItem.getRelativePath());
        fileInfoVO.setExt(fileTreeItem.getExt());
        fileInfoVO.setSize(fileTreeItem.getSize());


        templateTreeItemVO.setFileInfo(fileInfoVO);

        ArrayList<TemplateTreeItemVO> templateTreeItemVOList = new ArrayList<>();

        // 判断fileTreeItem是否有子集,如果有子集
        if (fileTreeItem.getChildList() != null) {
            // 遍历子集
            for (FileTreeItem treeItem : fileTreeItem.getChildList()) {

                TemplateTreeItemVO templateChildTreeItemVO = new TemplateTreeItemVO();
                p_templateTreeToVO(treeItem, templateChildTreeItemVO, templateRootPath);
                // 没有子集或者递归出来了，就添加到
                templateTreeItemVOList.add(templateChildTreeItemVO);
            }
        }

        // 将集合添加到对象templateTreeItemVO中
        templateTreeItemVO.setChildList(templateTreeItemVOList);
    }


    /**
     * 将文件数转换为html的VO对象
     * @param fileTreeItem
     * @param htmlTemplateTreeItemVO
     */
    private void p_htmlTemplateTreeToVO(FileTreeItem fileTreeItem, HtmlTemplateTreeItemVO htmlTemplateTreeItemVO, String templateRootPath) {
        // 不是文件夹并且不是html文件的不添加
        if (0 == fileTreeItem.getIsDir() && !"html".equals(fileTreeItem.getExt())) {
            return;
        }

        // 设置vo的值
        htmlTemplateTreeItemVO.setTitle(fileTreeItem.getFileName());
        htmlTemplateTreeItemVO.setIsDir(fileTreeItem.getIsDir());
        htmlTemplateTreeItemVO.setExt(fileTreeItem.getExt());
        if (null != fileTreeItem.getRelativePath()) {
            htmlTemplateTreeItemVO.setPath(templateRootPath + fileTreeItem.getRelativePath());
        }

        ArrayList<HtmlTemplateTreeItemVO> htmlTemplateTreeItemVOList = new ArrayList<>();

        // 判断fileTreeItem是否有子集,如果有子集
        if (fileTreeItem.getChildList() != null) {
            // 遍历子集
            for (FileTreeItem treeItem : fileTreeItem.getChildList()) {
                if (0 == treeItem.getIsDir() && !"html".equals(treeItem.getExt())) {
                    continue;
                }

                HtmlTemplateTreeItemVO templateChildTreeItemVO = new HtmlTemplateTreeItemVO();
                p_htmlTemplateTreeToVO(treeItem, templateChildTreeItemVO, templateRootPath);
                // 没有子集或者递归出来了，就添加到
                htmlTemplateTreeItemVOList.add(templateChildTreeItemVO);
            }
        }

        // 将集合添加到对象templateTreeItemVO中
        htmlTemplateTreeItemVO.setChildList(htmlTemplateTreeItemVOList);
    }

    @Override
    public boolean createTemplateDir(String path, String dirName) {
        return LocalFileUtil.createDir(path, dirName);
    }

    @Override
    public boolean deleteTemplateDir(String pathName) {

        return LocalFileUtil.deleteDir(pathName);
    }

    @Override
    public boolean createTemplateFile(String path, String fileName) {
        fileName +=  ".html";
        return LocalFileUtil.createFile(path, fileName);
    }

    @Override
    public boolean deleteTemplateFile(String pathName) {
        return LocalFileUtil.deleteFile(pathName);
    }


    @Override
    public boolean setFileContent(String path, String content) throws IOException {
        return LocalFileUtil.setFileContent(path, content);
    }

    @Override
    public StringBuffer getFileContent(String path) throws IOException {
        StringBuffer fileContent = LocalFileUtil.getFileContent(path);
        return fileContent;
    }

    @Override
    public File downloadFileContent(String path,  HttpServletResponse response) throws IOException {
        File file = LocalFileUtil.downloadFile(path, response);
        return file;
    }

    @Override
    public boolean uploadFileContent(String path, MultipartFile file) throws IOException {
        return LocalFileUtil.uploadFileContent(path, file);
    }
}
